home *** CD-ROM | disk | FTP | other *** search
/ Introduction to 3D Game …ogramming with DirectX 12 / Introduction-to-3D-Game-Programming-with-DirectX-12.ISO / Code.Textures / Chapter 13 The Compute Shader / SobelFilter / SobelFilter.cpp < prev    next >
Encoding:
C/C++ Source or Header  |  2016-03-02  |  4.1 KB  |  129 lines

  1. //***************************************************************************************
  2. // SobelFilter.cpp by Frank Luna (C) 2011 All Rights Reserved.
  3. //***************************************************************************************
  4.  
  5. #include "SobelFilter.h"
  6.  
  7. SobelFilter::SobelFilter(ID3D12Device* device, 
  8.                        UINT width, UINT height,
  9.                        DXGI_FORMAT format)
  10. {
  11.     md3dDevice = device;
  12.  
  13.     mWidth = width;
  14.     mHeight = height;
  15.     mFormat = format;
  16.  
  17.     BuildResource();
  18. }
  19.  
  20. CD3DX12_GPU_DESCRIPTOR_HANDLE SobelFilter::OutputSrv()
  21. {
  22.     return mhGpuSrv;
  23. }
  24.  
  25. UINT SobelFilter::DescriptorCount()const
  26. {
  27.     return 2;
  28. }
  29.  
  30. void SobelFilter::BuildDescriptors(CD3DX12_CPU_DESCRIPTOR_HANDLE hCpuDescriptor,
  31.                                   CD3DX12_GPU_DESCRIPTOR_HANDLE hGpuDescriptor,
  32.                                   UINT descriptorSize)
  33. {
  34.     // Save references to the descriptors. 
  35.     mhCpuSrv = hCpuDescriptor;
  36.     mhCpuUav = hCpuDescriptor.Offset(1, descriptorSize);
  37.     mhGpuSrv = hGpuDescriptor;
  38.     mhGpuUav = hGpuDescriptor.Offset(1, descriptorSize);
  39.  
  40.     BuildDescriptors();
  41. }
  42.  
  43. void SobelFilter::OnResize(UINT newWidth, UINT newHeight)
  44. {
  45.     if((mWidth != newWidth) || (mHeight != newHeight))
  46.     {
  47.         mWidth = newWidth;
  48.         mHeight = newHeight;
  49.  
  50.         BuildResource();
  51.  
  52.         // New resource, so we need new descriptors to that resource.
  53.         BuildDescriptors();
  54.     }
  55. }
  56.  
  57. void SobelFilter::Execute(ID3D12GraphicsCommandList* cmdList, 
  58.                          ID3D12RootSignature* rootSig,
  59.                          ID3D12PipelineState* pso,
  60.                          CD3DX12_GPU_DESCRIPTOR_HANDLE input)
  61. {
  62.     cmdList->SetComputeRootSignature(rootSig);
  63.     cmdList->SetPipelineState(pso);
  64.  
  65.     cmdList->SetComputeRootDescriptorTable(0, input);
  66.     cmdList->SetComputeRootDescriptorTable(2, mhGpuUav);
  67.  
  68.     cmdList->ResourceBarrier(1, &CD3DX12_RESOURCE_BARRIER::Transition(mOutput.Get(),
  69.         D3D12_RESOURCE_STATE_GENERIC_READ, D3D12_RESOURCE_STATE_UNORDERED_ACCESS));
  70.  
  71.     // How many groups do we need to dispatch to cover image, where each
  72.     // group covers 16x16 pixels.
  73.     UINT numGroupsX = (UINT)ceilf(mWidth / 16.0f);
  74.     UINT numGroupsY = (UINT)ceilf(mHeight / 16.0f);
  75.     cmdList->Dispatch(numGroupsX, numGroupsY, 1);
  76.  
  77.     cmdList->ResourceBarrier(1, &CD3DX12_RESOURCE_BARRIER::Transition(mOutput.Get(),
  78.         D3D12_RESOURCE_STATE_UNORDERED_ACCESS, D3D12_RESOURCE_STATE_GENERIC_READ));
  79. }
  80.  
  81. void SobelFilter::BuildDescriptors()
  82. {
  83.     D3D12_SHADER_RESOURCE_VIEW_DESC srvDesc = {};
  84.     srvDesc.Shader4ComponentMapping = D3D12_DEFAULT_SHADER_4_COMPONENT_MAPPING;
  85.     srvDesc.Format = mFormat;
  86.     srvDesc.ViewDimension = D3D12_SRV_DIMENSION_TEXTURE2D;
  87.     srvDesc.Texture2D.MostDetailedMip = 0;
  88.     srvDesc.Texture2D.MipLevels = 1;
  89.  
  90.     D3D12_UNORDERED_ACCESS_VIEW_DESC uavDesc = {};
  91.  
  92.     uavDesc.Format = mFormat;
  93.     uavDesc.ViewDimension = D3D12_UAV_DIMENSION_TEXTURE2D;
  94.     uavDesc.Texture2D.MipSlice = 0;
  95.  
  96.     md3dDevice->CreateShaderResourceView(mOutput.Get(), &srvDesc, mhCpuSrv);
  97.     md3dDevice->CreateUnorderedAccessView(mOutput.Get(), nullptr, &uavDesc, mhCpuUav);
  98. }
  99.  
  100. void SobelFilter::BuildResource()
  101. {
  102.     // Note, compressed formats cannot be used for UAV.  We get error like:
  103.     // ERROR: ID3D11Device::CreateTexture2D: The format (0x4d, BC3_UNORM) 
  104.     // cannot be bound as an UnorderedAccessView, or cast to a format that
  105.     // could be bound as an UnorderedAccessView.  Therefore this format 
  106.     // does not support D3D11_BIND_UNORDERED_ACCESS.
  107.  
  108.     D3D12_RESOURCE_DESC texDesc;
  109.     ZeroMemory(&texDesc, sizeof(D3D12_RESOURCE_DESC));
  110.     texDesc.Dimension = D3D12_RESOURCE_DIMENSION_TEXTURE2D;
  111.     texDesc.Alignment = 0;
  112.     texDesc.Width = mWidth;
  113.     texDesc.Height = mHeight;
  114.     texDesc.DepthOrArraySize = 1;
  115.     texDesc.MipLevels = 1;
  116.     texDesc.Format = mFormat;
  117.     texDesc.SampleDesc.Count = 1;
  118.     texDesc.SampleDesc.Quality = 0;
  119.     texDesc.Layout = D3D12_TEXTURE_LAYOUT_UNKNOWN;
  120.     texDesc.Flags = D3D12_RESOURCE_FLAG_ALLOW_UNORDERED_ACCESS;
  121.  
  122.     ThrowIfFailed(md3dDevice->CreateCommittedResource(
  123.         &CD3DX12_HEAP_PROPERTIES(D3D12_HEAP_TYPE_DEFAULT),
  124.         D3D12_HEAP_FLAG_NONE,
  125.         &texDesc,
  126.         D3D12_RESOURCE_STATE_GENERIC_READ,
  127.         nullptr,
  128.         IID_PPV_ARGS(&mOutput)));
  129. }